<?php

namespace App\Services;

use Illuminate\Support\Str;
use Illuminate\Support\Facades\File;
use Illuminate\Support\Facades\Http;
use Illuminate\Support\Facades\Log;

class QrCodeService
{
    /**
     * 生成二维码图片
     * 
     * @param string $data
     * @return string 生成的二维码文件路径
     */
    public function generate($data)
    {
        Log::info('开始生成二维码', ['data_length' => strlen($data)]);
        
        // 生成唯一文件名
        $filename = 'qrcodes/' . Str::uuid() . '.png';
        $path = public_path('storage/' . $filename);
        
        Log::info('二维码文件路径', ['path' => $path]);
        
        // 确保目录存在
        $directory = dirname($path);
        if (!is_dir($directory)) {
            File::makeDirectory($directory, 0755, true);
            Log::info('创建目录', ['directory' => $directory]);
        }
        
        try {
            // 获取微信接口调用凭证
            Log::info('获取微信AccessToken');
            $wechatService = app(WechatService::class);
            $accessToken = $wechatService->getAccessToken();
            Log::info('获取AccessToken成功', ['token_length' => strlen($accessToken)]);
            
            // 使用微信小程序码API生成不限制数量的小程序码
            $url = "https://api.weixin.qq.com/wxa/getwxacodeunlimit?access_token={$accessToken}";
            
            // 将数据编码到scene中，最大长度为32位
            $scene = substr(md5($data), 0, 32);
            Log::info('生成scene参数', ['scene' => $scene]);
            
            $response = Http::post($url, [
                'scene' => $scene,
                'page' => 'pages/scanResult/scanResult',  // 扫码后跳转的页面
                'check_path' => false,  // 如果页面不存在也不报错
                'env_version' => 'release',  // 默认正式版
                'width' => 400  // 二维码的宽度
            ]);
            
            Log::info('微信API响应', [
                'status' => $response->status(),
                'body_length' => strlen($response->body())
            ]);
            
            // 微信返回的是图片二进制内容，不是JSON
            if ($response->status() === 200 && !$this->isErrorResponse($response->body())) {
                File::put($path, $response->body());
                Log::info('二维码文件保存成功', ['file_size' => filesize($path)]);
            } else {
                $error = json_decode($response->body(), true);
                Log::error('微信生成二维码失败', $error ?? ['body' => $response->body()]);
                throw new \Exception('生成二维码失败: ' . ($error['errmsg'] ?? '未知错误'));
            }
            
            // 将scene和数据的对应关系保存到数据库
            $this->saveSceneMapping($scene, $data);
            
            Log::info('二维码生成完成', ['return_path' => 'storage/' . $filename]);
            return 'storage/' . $filename;
        } catch (\Exception $e) {
            Log::error('生成二维码失败', ['error' => $e->getMessage()]);
            throw $e;
        }
    }
    
    /**
     * 判断返回内容是否为错误信息（微信错误返回JSON，成功返回图片）
     */
    private function isErrorResponse($body)
    {
        // 尝试解析JSON，如果能解析并包含errcode字段则认为是错误
        $data = json_decode($body, true);
        return $data && isset($data['errcode']) && $data['errcode'] != 0;
    }
    
    /**
     * 保存scene和原始数据的映射关系
     */
    private function saveSceneMapping($scene, $data)
    {
        // 可以使用Redis或数据库保存映射关系
        // 这里简单使用缓存保存
        \Illuminate\Support\Facades\Cache::put("qrcode_scene:{$scene}", $data, now()->addMonths(6));
    }
} 